/**
 * Copyright ©2012-2018 HopeHaiyang Corporation, All Rights Reserved
 * http://www.wuhanhope.com
 */
package hope.platform.data.server.data.img;

import hope.platform.data.dao.SiteDistanceRepository;
import hope.platform.data.dao.SiteInfoRepository;
import hope.platform.data.domain.SiteDistance;
import hope.platform.data.domain.SiteInfo;
import hope.platform.data.server.data.header.SiteDistanceService;
import hope.platform.data.utils.DistanceUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.Collection;
import java.util.Date;
import java.util.List;

/**
 * class info
 *
 * @author hujia
 *         Create at 2018/7/11 15:57
 */
@Service
public class SiteDistanceServiceImg implements SiteDistanceService {

    @Autowired
    private SiteDistanceRepository siteDistanceRepository;

    @Autowired
    private SiteInfoRepository siteInfoRepository;

    @Override
    public List<SiteDistance> getSiteDistancesBySerialNumber(String serialNumber) {
        return siteDistanceRepository.findBySerialNumber(serialNumber);
    }

    @Override
    public void addBySiteInfo(SiteInfo siteInfo) throws Exception {
        siteInfo.setGmtCreate(new Date());
        siteInfo.setGmtModified(new Date());
        checkValue(siteInfo);
        saveSiteInfo(siteInfo);
    }


    @Override
    public void updateBySiteInfo(SiteInfo siteInfo) throws Exception {
        checkValue(siteInfo);
        updateSiteInfo(siteInfo);
    }

    @Override
    public List<SiteDistance> getBySerialNumberAndDistanceBetween(String serialNumber, Double small,
                                                                  Double big) {
        return this.siteDistanceRepository.findBySerialNumberAndDistanceBetween(serialNumber, small, big);
    }

    public void checkValue(SiteInfo siteInfo) throws Exception {
        if (null == siteInfo.getLongitude() || null == siteInfo.getLatitude()) {
            if (siteInfo.getId() != null) {
                SiteInfo tmp = siteInfoRepository.findBySerialNumber(siteInfo.getSerialNumber());
                siteInfo.setLongitude(tmp.getLongitude());
                siteInfo.setLatitude(tmp.getLatitude());
            } else {
                throw new Exception("siteInfo attribute is null.");
            }
        }
    }

    public void saveSiteInfo(SiteInfo mainSite) {
        Collection<SiteInfo> siteInfos = siteInfoRepository.findAll();
        for (SiteInfo siteInfo : siteInfos) {
            if (siteInfo.getSerialNumber().equals(mainSite.getSerialNumber())) {
                continue;
            }
            saveData(mainSite, siteInfo);
            saveData(siteInfo, mainSite);
        }
    }

    public void updateSiteInfo(SiteInfo mainSite) throws Exception {
        Collection<SiteInfo> siteInfos = siteInfoRepository.findAll();
        for (SiteInfo siteInfo : siteInfos) {
            if (mainSite.getSerialNumber().equals(siteInfo.getSerialNumber())) {
                continue;
            }
            updateData(mainSite, siteInfo);
            updateData(siteInfo, mainSite);
        }
    }

    private void updateData(SiteInfo mainSite, SiteInfo siteInfo) {
        SiteDistance siteDistance = siteDistanceRepository.findBySerialNumberAndOtherSerialNumber(
                mainSite.getSerialNumber(), siteInfo.getSerialNumber());
        save(siteDistance, mainSite, siteInfo);
    }

    public void saveData(SiteInfo mainSite, SiteInfo siteInfo) {
        SiteDistance siteDistance = new SiteDistance();
        save(siteDistance, mainSite, siteInfo);
    }

    public void save(SiteDistance siteDistance, SiteInfo mainSite, SiteInfo siteInfo) {
        siteDistance.setSerialNumber(mainSite.getSerialNumber());
        siteDistance.setOtherSerialNumber(siteInfo.getSerialNumber());
        double distance = DistanceUtils.TwoPointByLatitudeAndLongitude(mainSite.getLongitude(),
                mainSite.getLatitude(), siteInfo.getLongitude(), siteInfo.getLatitude());
        distance /= 1000;
        siteDistance.setDistance(distance);
        siteDistanceRepository.save(siteDistance);
    }
}
